#ifndef __CONFIG_H__
#define __CONFIG_H__
#include "sfsis.h"
#include "config_mode.h"
#include "config_modeFactory.h"
#include "config_factory.h"
#include "config_common.h"
#include "config_firmware.h"
#include "config_wireless.h"
#pragma pack(1)
#define CONFIG_OFFSET(TYPE, MEMBER) ((su32)(&((TYPE *)0)->MEMBER))
/*配置文件的总体约定:
  配置文件在本地使用时，大部分都是通过结构体来使用的。
  当外部进行配置时，调用setReg和getReg在配置管理器不仅对配置文件的权限进行检查，而且对非易失存储也做处理。
  设计中避免暴露config的操作
*/
typedef enum
{
    CONFIG_COMMON,
    CONFIG_MODE,
    CONFIG_MODEFACTORY,
    CONFIG_FACTORY,
    CONFIG_FIRMWARE,
    CONFIG_WIRELESS,
    CONFIG_BLANK,
} Config_Type;

/*配置文件总体*/
typedef struct
{
    Config_Common_u common;           //address start @0
    Config_Mode_u mode;               //address start @32
    Config_ModeFactory_u modeFactory; //address start @96
    Config_Factory_u factory;         //address start @160
    Config_Firmware_u firmware;       //address start @224
    Config_Wireless_u wireless;       //address start @248
    su8 reserved[2];
} Config;

typedef enum
{
    CONFIG_MAP_COMMON_HEAD = 0,
    CONFIG_MAP_COMMON_TAIL = (sizeof(Config_Common_u)) - 1,

    CONFIG_MAP_MODE_HEAD = (sizeof(Config_Common_u)),
    CONFIG_MAP_MODE_TAIL = CONFIG_MAP_MODE_HEAD + sizeof(Config_Mode_u) - 1,

    CONFIG_MAP_MODEFACTORY_HEAD = CONFIG_MAP_MODE_HEAD + sizeof(Config_Mode_u),
    CONFIG_MAP_MODEFACTORY_TAIL = CONFIG_MAP_MODEFACTORY_HEAD + sizeof(Config_ModeFactory_u) - 1,

    CONFIG_MAP_FACTORY_HEAD = CONFIG_MAP_MODEFACTORY_HEAD + sizeof(Config_ModeFactory_u),
    CONFIG_MAP_FACTORY_TAIL = CONFIG_MAP_FACTORY_HEAD + sizeof(Config_Factory_u) - 1,

    CONFIG_MAP_FIRMWARE_HEAD = CONFIG_MAP_FACTORY_HEAD + sizeof(Config_Factory_u),
    CONFIG_MAP_FIRMWARE_TAIL = CONFIG_MAP_FIRMWARE_HEAD + sizeof(Config_Firmware_u) - 1,

    CONFIG_MAP_WIRELESS_HEAD = CONFIG_MAP_FIRMWARE_HEAD + sizeof(Config_Firmware_u),
    CONFIG_MAP_WIRELESS_TAIL = CONFIG_MAP_WIRELESS_HEAD + sizeof(Config_Wireless_u) - 1,
    /*blank 区域为黑区，目前存了两个字节，用于debug中的调试信息状态存储，详见debug.c*/
    CONFIG_MAP_BLANK_HEAD = CONFIG_MAP_WIRELESS_HEAD + sizeof(Config_Wireless_u),
    CONFIG_MAP_BLANK_TAIL = 255,
} Config_Map;

typedef union //配置参数联合体
{
    Config entity;
    su8 memory[256];
} Config_u;

typedef enum
{
    AUTH_CFG_DIRECT = 0,       //直接模式，寄存器会被写入ram和flash
    AUTH_CFG_INDIRECT = 1,     //间接模式，寄存器会被写入ram，但要通过操作shaodow reset 对应才可操作
    AUTH_CFG_SHADOW = 2,       //影子模式，寄存器仅写入影子寄存器
    AUTH_CFG_SHADOW_RESET = 3, //寄存器仅写入影子寄存器，编程后会立即复位,一般用来做一些特殊处理的寄存器会使用该值
    AUTH_CFG_READONLY = 4,     //只读，不可写
} Auth_Type;

#pragma pack()
extern Config_u gCfg_u;
extern Config *gCfgPtr;                        //全局配置指针
extern Config_Wireless *gCfgWirelessPtr;       //全局无线配置指针
extern Config_Common *gCfgCommonPtr;           //通用配置指针
extern Config_Factory *gCfgFactoryPtr;         //工厂出厂配置指针
extern Config_Firmware *gCfgFirmwarePtr;       //固件参数配置指针
extern Config_Mode *gCfgModePtr;               //模式配置指针
extern Config_ModeFactory *gCfgModeFactoryPtr; //模式工厂配置指针
extern const Config_u gSCfg_u;                 //全局静态配置，属于默认配置
extern const Auth_Type regAuth_Mask[256];
void config_default(Config *config);
void config_init(void);


//接口供外部烧写使用，有较高安全性
SF_Boolen config_setReg(su8 address, su8 value);
SF_Boolen config_setMultRegs(su8 startAddress, su8 *buf, su8 count);
su8 config_getReg(su8 address);
su8 config_getMultRegs(su8 startAddress, su8 *buf, su8 getLen);


/*根据指定的type刷新配置*/
//仅内部使用接口，将固定块的配置刷入非易失存储，如果不支持刷入的，会直接返回SF_False
//注:该接口不用关注读写安全位和配置合法性，有一定危险性
//该接口危险性较高，谨慎使用
SF_Boolen config_flush(Config_Type cfgType);
void config_restore(Config_Type cfgType);
/*将某个配置恢复*/

#endif
